package com.sts.common.utils;

import cn.hutool.core.date.DateUtil;
import cn.hutool.core.exceptions.ExceptionUtil;
import cn.hutool.core.lang.Singleton;
import cn.hutool.core.util.StrUtil;
import com.sts.Main;
import com.sts.common.threadpool.VirtualThreadPool;
import lombok.extern.slf4j.Slf4j;

import javax.swing.*;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.StringReader;
import java.util.Objects;
import java.util.concurrent.CompletableFuture;

/**
 * @author lsl
 * @since 2025年07月15日 18:50
 */
@Slf4j
public class CompletableFutureUtil {

    private static final VirtualThreadPool virtualThreadPool = Singleton.get(VirtualThreadPool.class);

    public static void runAndThrowException(Runnable runnable) {
        CompletableFuture.runAsync(runnable, virtualThreadPool.getExecutorService())
                .whenComplete((_, throwable) -> throwException(throwable, null));
    }

    public static void runAndThrowExceptionFrontPresent(Runnable runnable, PresentFunction frontPresentFunction, JTextArea logTextArea) {
        CompletableFuture.runAsync(runnable, virtualThreadPool.getExecutorService())
                .whenComplete((_, throwable) -> {
                    if (Objects.nonNull(frontPresentFunction)) {
                        frontPresentFunction.execute();
                    }
                    throwException(throwable, logTextArea);
                });
    }

    public static void throwException(Throwable throwable, JTextArea logTextArea) {
        if (Objects.nonNull(throwable)) {
            Throwable rootCause = ExceptionUtil.getRootCause(throwable);
            String errMsg = rootCause.getMessage();
            log.error(errMsg, rootCause);
            if (logTextArea != null) {
                logTextArea.append(DateUtil.now() + " - " + errMsg + "\n");
            }
            if (lineNumber(errMsg)) {
                JOptionPane.showMessageDialog(
                        Main.rootFrame,
                        errMsg,
                        "异常",
                        JOptionPane.ERROR_MESSAGE
                );
            } else {
                // todo 使用大的异常框
            }
        }
    }

    private static boolean lineNumber(String str) {
        // todo 根据错误信息的行数来判断使用什么错误信息提示框
        if (StrUtil.isBlank(str)) {
            return true;
        }
        // 如果行数大于3就返回false  否则就返回true
        try (BufferedReader br = new BufferedReader(new StringReader(str))) {
            int lines = 0;
            while (br.readLine() != null) {
                lines++;
                if (lines > 3) {
                    return false;
                }
            }
            return true;
        } catch (IOException e) {
            throw new RuntimeException(e.getMessage(), e);
        }
    }
}
